/*
 * $Id: tcp.h,v 1.22 2006-02-08 11:04:01 bacon Exp $
 */

#ifndef _XP_NET_TCP_H_
#define _XP_NET_TCP_H_

#include <xp/net/sck.h>
#include <xp/bas/time.h>
#include <xp/bas/tio.h>

enum
{
	XP_TCP_BINARY = 1,
	XP_TCP_TEXT   = 2
};

enum
{
	XP_TCP_ENOERR = 0,
	XP_TCP_ENOMEM, /* out of memory */
	XP_TCP_EINVAL, /* invalid argument, data, etc */
	XP_TCP_ETMOUT, /* operation timed out */
	XP_TCP_ESCKOP, /* failed to open a socket */
	XP_TCP_ESCKCL, /* failed to close a socket */
	XP_TCP_ESCKCN, /* failed to conn */
	XP_TCP_ESCKBN, /* failed to bind */
	XP_TCP_ESCKLS, /* failed to lstn */
	XP_TCP_ESCKAC, /* failed to acpt */
	XP_TCP_ESCKSN, /* failed to send */
	XP_TCP_ESCKRC, /* failed to recv */
	XP_TCP_ETIOOP, /* failed to open tio */
	XP_TCP_ETIOCL, /* failed to close tio */
	XP_TCP_ETIOAI, /* failed to attach input to tio */
	XP_TCP_ETIOAO  /* failed to attach output to tio */
};

enum
{
	XP_TCP_CONN = XP_SCK_CONN,
	XP_TCP_ACPT = XP_SCK_ACPT,
	XP_TCP_SEND = XP_SCK_SEND,
	XP_TCP_RECV = XP_SCK_RECV,
	XP_TCP_ALL  = XP_SCK_ALL
};

struct xp_tcp_t
{
	xp_sck_t* sck;
	xp_sck_t  __sck;
	int mode;

	xp_tio_t tio;
	int errnum;
	xp_bool_t __dynamic;
};

typedef struct xp_tcp_t xp_tcp_t;

#ifdef __cplusplus
extern "C" {
#endif

xp_tcp_t* xp_tcp_open (xp_tcp_t* tcp, int mode);
int xp_tcp_close (xp_tcp_t* tcp);

xp_sckhnd_t xp_tcp_gethnd (xp_tcp_t* tcp);

int xp_tcp_geterrnum (xp_tcp_t* tcp);
const xp_char_t* xp_tcp_geterrstr (xp_tcp_t* tcp);

xp_time_t xp_tcp_gettmout (xp_tcp_t* tcp, int object);
void xp_tcp_settmout (xp_tcp_t* tcp, int object, xp_time_t tmout);

void xp_tcp_setcancel (xp_tcp_t* tcp, 
	int object, xp_bool_t (*cancel) (void*), void* arg);

int xp_tcp_conn (xp_tcp_t* tcp, xp_uint16_t port, 
	const void* host, xp_size_t hostsz, xp_uint32_t scope_id);

int xp_tcp_bind (xp_tcp_t* tcp, xp_uint16_t port, 
	const void* host, xp_size_t hostsz, xp_uint32_t scope_id);
int xp_tcp_lstn (xp_tcp_t* tcp, int backlog);
xp_tcp_t* xp_tcp_acpt (xp_tcp_t* tcp, xp_tcp_t* client);

xp_ssize_t xp_tcp_send (xp_tcp_t* tcp, const void* data, xp_size_t size);
xp_ssize_t xp_tcp_recv (xp_tcp_t* tcp, void* buf, xp_size_t size);

#ifdef __cplusplus
}
#endif

#endif
